#!/usr/bin/env python
#coding:utf-8
# ref_blog:http://www.open-open.com/home/space-5679-do-blog-id-3247.html

import Queue
import threading
import time
import urllib2
class ThreadPool(object):
    """
    线程池的实现,管理线程
    """
    def __init__(self, pool_size=1):
        self.task_queue = Queue.Queue() #任务队列
        self.finish_queue = Queue.Queue() #结果队列
        self.pool_size = pool_size
        self.pool = []
        self.lock = threading.Lock() #线程锁
        self.running = 0
    #创建线程，并添加到pool中
    def create_threads(self,poolsize=None):
        if not poolsize:
            poolsize = self.pool_size
        elif poolsize!=self.pool_size:
            self.pool_size = poolsize
        for i in range(poolsize):
            self.pool.append(Work(self))
    #停止线程的运行
    def stop_threads(self):
        for thread in self.pool:
            thread.stop()
            thread.join()
        del self.pool[:]

    #添加task 到线程任务队列
    def add_task(self, func, *args,**kargs):
        self.task_queue.put((func, args, kargs))

    #从task队列中获取task
    def get_task(self, *args, **kargs):
        task = self.task_queue.get(*args, **kargs)
        return task
    #将task返回结果存入结果队列
    def put_task_result(self, *args):
        self.finish_queue.put(args)

    #获取已完成task的结果
    def get_task_result(self, *args, **kargs):
        return self.finish_queue.get(*args, **kargs)

    #通知系统task完成
    def task_done(self, *args, **kargs):
        self.task_queue.task_done()

    #等待所有task线程运行完毕
    def wait_allcomplete(self):
        for thread in self.pool:
            if thread.isAlive():thread.join()

    #任务运行计数器-加
    def add_running_num(self):
        self.lock.acquire()
        self.running += 1
        self.lock.release()

    #任务运行计数器-减
    def decrease_running_num(self):
        self.lock.acquire()
        self.running -= 1
        self.lock.release()

    def get_task_left(self):
        #线程池的所有任务包括：
        #task队列中未被运行的任务+已完成的任务+正在运行的任务
        return self.task_queue.qsize()+self.finish_queue._qsize()+self.running

class Work(threading.Thread):
    """
    线程的作业实现
    """
    def __init__(self, threadPool):
        threading.Thread.__init__(self)
        self.setDaemon(True)
        self.stat = 1 #正常状态，循环处理task
        self.threadPool = threadPool
        self.start()
    def stop(self):
        self.stat = 0
    def run(self):
        # loop，处理task
        while 1:
            if not self.stat:
                #检测到stop，关闭线程
                break
            try:
                func, args, kargs= self.threadPool.get_task(timeout=1,block=False)
            except Queue.Empty:
                #TODO 若用join 等待 线程有可能不退出(没有调用task_done)
                continue
            try:
                #计数器, running+1
                self.threadPool.add_running_num()
                ret = func(*args, **kargs)
                if ret:
                    self.threadPool.put_task_result(ret)
            except Exception,e:
                pass
            finally:
                #计数器, running-1
                self.threadPool.decrease_running_num()
                #通知系统 task 完成
                self.threadPool.task_done()
